package com.norns.torque.view

import android.content.ClipData
import android.content.ClipboardManager
import android.content.Context
import android.content.Intent
import android.os.Bundle
import android.os.Handler
import android.os.Looper
import android.text.TextUtils
import android.view.View
import android.widget.Toast
import androidx.activity.viewModels
import androidx.appcompat.app.AppCompatActivity
import androidx.collection.ArrayMap
import androidx.core.view.ViewCompat
import androidx.core.view.WindowInsetsCompat
import com.gyf.immersionbar.ImmersionBar
import com.hi.dhl.binding.viewbind
import com.norns.torque.BluetoothViewModel
import com.norns.torque.R
import com.norns.torque.bluetooth.ChatServer
import com.norns.torque.databinding.ActivitySettingBinding
import com.norns.torque.dialog.EditContentDialog
import com.norns.torque.dialog.EditWifiDialog
import com.norns.torque.dialog.PwdDialog
import com.norns.torque.dialog.WheelDialog
import com.norns.torque.entrty.DeviceConfig
import com.norns.torque.kvwrapper.SpUtil
import com.norns.torque.utils.AppConstant
import com.norns.torque.utils.AppContext
import com.norns.torque.utils.DataConversion
import com.norns.torque.utils.DataConversion.hexStringToByteArray
import timber.log.Timber
import java.lang.Float.intBitsToFloat
import java.nio.ByteBuffer
import java.nio.ByteOrder
import java.text.DecimalFormat
import java.time.LocalDateTime
import java.time.format.DateTimeFormatter


class SettingActivity : AppCompatActivity() {
    private val binding: ActivitySettingBinding by viewbind()
    private val viewModel: BluetoothViewModel by viewModels()
    private val optionsStr = ArrayMap<String, String>()
    private val timeLoop: Int = 1245
    override fun attachBaseContext(newBase: Context?) {
        super.attachBaseContext(newBase)
        overrideFontScale(newBase)
    }

    /**
     * 重置配置 fontScale：保持字体比例不变，始终为 1.
     */
    private fun overrideFontScale(context: Context?) {
        if (context == null) return
        context.resources.configuration.let {
            it.fontScale = 1f // 保持字体比例不变，始终为 1.
            applyOverrideConfiguration(it) // 应用新的配置
        }
    }


    private val handler: Handler = object : Handler(Looper.myLooper()!!) {
        override fun handleMessage(msg: android.os.Message) {
            if (msg.what == timeLoop) {
                val localDateTime = LocalDateTime.now()
                val f1 = DateTimeFormatter.ofPattern("yyyy年MM月dd日 HH:mm:ss")
                val contentTime = localDateTime.format(f1)
                binding.tvDate.setText(contentTime)
                sendEmptyMessageDelayed(timeLoop, 1000)
            }
        }
    }

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        initView()
        initData()
        subscribeToModel()
    }

    private fun initView() {
        ImmersionBar.with(this).statusBarColor(R.color.main)
            .navigationBarColor(R.color.white)
            .autoStatusBarDarkModeEnable(true, 0.2f)
            .init()
        ViewCompat.setOnApplyWindowInsetsListener(binding.root) { v, insets ->
            val systemBars = insets.getInsets(WindowInsetsCompat.Type.systemBars())
            v.setPadding(systemBars.left, systemBars.top, systemBars.right, systemBars.bottom)
            insets
        }
        if (ChatServer.contentType == ChatServer.NetWork) {
            binding.flRename.visibility = View.GONE
            binding.flNetwork.visibility = View.GONE
        } else {
            binding.flRename.visibility = View.VISIBLE
            binding.flNetwork.visibility = View.VISIBLE
        }
        binding.btnBack.setOnClickListener { finish() }

        binding.btnMore.setOnClickListener {
            viewModel.disconnect()
            if (ChatServer.contentType==ChatServer.NetWork) {
                startActivity(Intent(this@SettingActivity, WiFiDeviceActivity::class.java))
            }else{
                startActivity(Intent(this@SettingActivity, ScanActivity::class.java))
            }
            finish()
        }
        binding.btnTarget.setOnClickListener {
            if (!viewModel.isConnected()) {
                Toast.makeText(AppContext.context, "设备连接已断开", Toast.LENGTH_SHORT).show()
                return@setOnClickListener
            }
            //目标值
            val editContentDialog = EditContentDialog.newInstance(DeviceConfig.targetValue.toString(),"目标值",0)
            editContentDialog.setClickListener { value ->
                if (value.isEmpty().not()) {
                    val intValue = Integer.parseInt(value)
                    optionsStr.put(AppConstant.Target, value)
                    viewModel.setTargetValue(intValue)
                }
            }
            editContentDialog.show(supportFragmentManager, "EditContentDialog")
        }

        binding.btnPrecision.setOnClickListener {
            if (!viewModel.isConnected()) {
                Toast.makeText(AppContext.context, "设备连接已断开", Toast.LENGTH_SHORT).show()
                return@setOnClickListener
            }
            val wheelDialog = WheelDialog.newInstance(1)
            wheelDialog.setClickListener { value ->
                optionsStr.put(AppConstant.Precision, value.toString())
                viewModel.setPrecisionValue(value)
            }
            wheelDialog.show(supportFragmentManager, "WheelDialog")
        }
        binding.btnUnit.setOnClickListener {
            if (!viewModel.isConnected()) {
                Toast.makeText(AppContext.context, "设备连接已断开", Toast.LENGTH_SHORT).show()
                return@setOnClickListener
            }
            val wheelDialog = WheelDialog.newInstance(2)
            wheelDialog.setClickListener { value ->
                optionsStr.put(AppConstant.Unit, value.toString())
                viewModel.setUnitValue(value)
            }
            wheelDialog.show(supportFragmentManager, "WheelDialog")
        }
        binding.btnDate.setOnClickListener {
            if (!viewModel.isConnected()) {
                Toast.makeText(AppContext.context, "设备连接已断开", Toast.LENGTH_SHORT).show()
                return@setOnClickListener
            }
            parseDate()
        }

        binding.btnRename.setOnClickListener {
            if (!viewModel.isConnected()) {
                Toast.makeText(AppContext.context, "设备连接已断开", Toast.LENGTH_SHORT).show()
                return@setOnClickListener
            }
            val editContentDialog = EditContentDialog.newInstance(DeviceConfig.bluetoothName,"重命名")
            editContentDialog.setClickListener { value ->
                if (value.isEmpty().not()) {
                    optionsStr.put(AppConstant.BLUENAME, value)
                    viewModel.setRenameValue(value)
                }
            }
            editContentDialog.show(supportFragmentManager, "EditContentDialog")
        }
        binding.btnNetWork.setOnClickListener {
            if (!viewModel.isConnected()) {
                Toast.makeText(AppContext.context, "设备连接已断开", Toast.LENGTH_SHORT).show()
                return@setOnClickListener
            }
            val wifi = SpUtil.getString(AppConstant.WifiName, "")
            val pwd = SpUtil.getString(AppConstant.PWD, "")
            val wifiDialog = EditWifiDialog.newInstance(wifi, pwd)
            wifiDialog.setClickListener { wifiString, pwdString ->
                optionsStr.put(AppConstant.WifiName, wifiString)
                optionsStr.put(AppConstant.PWD, pwdString)

                SpUtil.saveString(AppConstant.WifiName, wifiString)
                SpUtil.saveString(AppConstant.PWD, pwdString)
                viewModel.setWiFiAndPwd(wifiString, pwdString)
            }
            wifiDialog.show(supportFragmentManager, "EditContentDialog")
        }

        binding.btnReset.setOnClickListener {
            if (!viewModel.isConnected()) {
                Toast.makeText(AppContext.context, "设备连接已断开", Toast.LENGTH_SHORT).show()
                return@setOnClickListener
            }
            val pwdDialog=PwdDialog.newInstance()
            pwdDialog.setClickListener { r->
                if (r){
                    viewModel.setResetValue()
                }
            }
            pwdDialog.show(supportFragmentManager,"pwdDialog")
        }
    }

    private fun initData() {
        val wifiName = SpUtil.getString(AppConstant.WifiName, "")
        if (wifiName.isEmpty()) {
            SpUtil.saveString(AppConstant.PWD, "")
        }
        binding.tvIPValue.text = wifiName
        binding.tvName.text = DeviceConfig.bluetoothName
        val localDateTime = LocalDateTime.now()
        val f1 = DateTimeFormatter.ofPattern("yyyy年MM月dd日 HH:mm:ss")
        val contentTime = localDateTime.format(f1)
        binding.tvDate.setText(contentTime)
        handler.sendEmptyMessage(timeLoop)
        viewModel.setResultMessageState(false)
        viewModel.readDeviceValue()
    }

    override fun onPause() {
        viewModel.removeListener()
        super.onPause()
    }

    override fun onDestroy() {
        super.onDestroy()
        handler.removeCallbacksAndMessages(null)
    }
    private fun parseDate() {
        val localDateTime = LocalDateTime.now()
        val hour: Int = localDateTime.getHour()
        val minute: Int = localDateTime.getMinute() // Calendar.MONTH 从0开始计数
        val second: Int = localDateTime.getSecond()
        val hourStr = if (hour < 10) {
            "0${hour}"
        } else {
            hour.toString()
        }
        val minuteStr = if (minute < 10) {
            "0${minute}"
        } else {
            minute.toString()
        }
        val secondStr = if (second < 10) {
            "0${second}"
        } else {
            second.toString()
        }
        //val cmdStr = "${hourStr}${minuteStr}${secondStr}"
        val year: Int = localDateTime.getYear()
        val month: Int = localDateTime.getMonth().getValue() // Calendar.MONTH 从0开始计数
        val day: Int = localDateTime.getDayOfMonth()
        val monthStr = if (month < 10) {
            "0${month}"
        } else {
            month.toString()
        }
        val dayStr = if (day < 10) {
            "0${day}"
        } else {
            day.toString()
        }

        val cmdStr = "${year-2000}${monthStr}${dayStr}${hourStr}${minuteStr}${secondStr}"
        viewModel.setDateValue(cmdStr)
    }

    private fun subscribeToModel() {
        //获取蓝牙发送的消息
        viewModel.messages.observe(this) { messages ->
            if (messages.startsWith("AA44")){
                val cmdCodeLengthStr = messages.substring(6, 8)
                val cmdCodeLength = Integer.parseInt(cmdCodeLengthStr, 16) * 2
                Timber.d("命令长度${cmdCodeLength}")
                if (messages.length <(8 + cmdCodeLength)){
                    lastMessage=messages
                }else{
                    parseMessage(messages)
                }
            }else{
                if (messages.endsWith("0D0A") && !TextUtils.isEmpty(lastMessage)){
                    lastMessage+=messages
                    Timber.d("2222:${lastMessage}")
                    parseMessage(lastMessage)
                }
            }
        }
        viewModel.connectionState.observe(this) { value ->
            if (value == AppConstant.connectionField) {
                Toast.makeText(AppContext.context, "设备连接已断开", Toast.LENGTH_SHORT).show()
            }
        }
    }
    private var lastMessage:String=""
    private fun parseMessage(messageText: String) {
        lastMessage=""
        if (messageText.startsWith("AA44")) {
            val cmdCodeStr = messageText.substring(4, 6)
            val cmdCode = cmdCodeStr.toInt(16)
            val cmdCodeLengthStr = messageText.substring(6, 8)
            val cmdCodeLength = cmdCodeLengthStr.toInt(16) * 2
            val cmdDataStr = try{
                messageText.substring(8, 8 + cmdCodeLength)
            }catch (e:Exception){
                ""
            }
            if (cmdDataStr.isEmpty()){// 获取剪贴板管理器
                val clipboard: ClipboardManager? = AppContext.context.getSystemService(Context.CLIPBOARD_SERVICE) as? ClipboardManager
                if (clipboard != null) {
                    // 创建一个剪贴数据对象并设置要复制的文本
                    val clip = ClipData.newPlainText("label", messageText)
                    // 将剪贴数据对象复制到剪贴板
                    clipboard.setPrimaryClip(clip)
                    // 提示用户复制成功
                    //Toast.makeText(applicationContext, "已复制到剪贴板", Toast.LENGTH_SHORT).show()
                }
                Toast.makeText(this, "设备命令错误", Toast.LENGTH_SHORT).show()
                return
            }
            val cmdData = if (cmdCode!=255){
                cmdDataStr.toInt(16)
            }else{
                1
            }
            when (cmdCode) {
                255 -> {//读取设备值
                    viewModel.setResultMessageState(true)
                    praceConfig(cmdDataStr)
                }
                1 -> {//设置目标值
                    if (cmdData == 2) {
                        val value = optionsStr[AppConstant.Target] ?: "0"
                        binding.tvTargetValue.text = value
                        DeviceConfig.targetValue = value.toInt()
                        Toast.makeText(this, "设置目标值成功", Toast.LENGTH_SHORT)
                            .show()
                    } else {
                        Toast.makeText(this, "设置目标值失败", Toast.LENGTH_SHORT)
                            .show()
                    }
                }

                2 -> {//设置精度
                    if (cmdData == 2) {
                        val value = optionsStr[AppConstant.Precision] ?: "0"
                        binding.tvPrecisionValue.text = value
                        DeviceConfig.precisionValue = value.toInt()
                        Toast.makeText(this, "设置精度成功", Toast.LENGTH_SHORT)
                            .show()
                    } else {
                        Toast.makeText(this, "设置精度失败", Toast.LENGTH_SHORT).show()
                    }
                }

                3 -> {//设置单位
                    if (cmdData == 2) {
                        val value = optionsStr[AppConstant.Unit] ?: "0"
                        binding.tvUnitValue.text =
                            viewModel.getUnitString(value.toInt())
                        DeviceConfig.unitValue = value.toInt()
                        Toast.makeText(this, "设置单位成功", Toast.LENGTH_SHORT).show()
                    } else {
                        Toast.makeText(this, "设置单位失败", Toast.LENGTH_SHORT).show()
                    }
                }

                4 -> {//设置日期
                    if (cmdData == 2) {
                        Toast.makeText(this, "对时成功", Toast.LENGTH_SHORT).show()
                    } else {
                        Toast.makeText(this, "对时失败", Toast.LENGTH_SHORT).show()
                    }
                }


                6 -> {//设置名称
                    if (cmdData == 2) {
                        val value = optionsStr[AppConstant.BLUENAME] ?: " "
                        SpUtil.saveString(AppConstant.BLUENAME, value)
                        binding.tvName.text = value
                        DeviceConfig.bluetoothName = value
                        ChatServer.updateBluetoothName(value)
                        Toast.makeText(this, "设置名称成功", Toast.LENGTH_SHORT).show()
                    } else {
                        Toast.makeText(this, "设置名称失败", Toast.LENGTH_SHORT).show()
                    }
                }

                7 -> {//恢复出厂设置
                    if (cmdData == 2) {
                        viewModel.readDeviceValue()
                        Toast.makeText(this, "恢复出厂设置成功", Toast.LENGTH_SHORT).show()
                    } else {
                        Toast.makeText(this, "恢复出厂设置失败", Toast.LENGTH_SHORT)
                            .show()
                    }
                }

                10 -> {//设置wifi 密码
                    if (cmdData == 2) {
                        val wifiName = optionsStr[AppConstant.WifiName] ?: " "
                        binding.tvIPValue.text = wifiName
                        Toast.makeText(this, "配置网络成功", Toast.LENGTH_SHORT).show()
                    } else {
                        Toast.makeText(this, "配置网络失败", Toast.LENGTH_SHORT).show()
                    }
                }
            }
        }
    }
    private fun praceConfig(cmdDataStr:String){
       val rangValueStr=cmdDataStr.substring(0,4)
       DeviceConfig.range=rangValueStr.toInt(16)
       //目标值
       val targetValueStr=cmdDataStr.substring(4,8)
       Timber.d("设备目标值:${targetValueStr}")
       DeviceConfig.targetValue=targetValueStr.toInt(16)
       binding.tvTargetValue.text = DeviceConfig.targetValue.toString()
       //精度
       val precisionValueStr=cmdDataStr.substring(8,10)
       Timber.d("设备精度值:${precisionValueStr}")
       DeviceConfig.precisionValue=precisionValueStr.toInt(16)
       binding.tvPrecisionValue.text = DeviceConfig.precisionValue.toString()
       //单位
       val unitStr=cmdDataStr.substring(10,12)
       Timber.d("设备单位值:${unitStr}")
       DeviceConfig.unitValue=unitStr.toInt(16)
       binding.tvUnitValue.text = viewModel.getUnitString(DeviceConfig.unitValue)

       if (cmdDataStr.length<=24){
           DeviceConfig.bluetoothName=ChatServer.contentDevice.value?.name?:"Unknown"
           binding.tvName.text = DeviceConfig.bluetoothName
       }else{
           val deviceNameCode=cmdDataStr.substring(24)
           val deviceName=DataConversion.hexStringToOriginalString(deviceNameCode)
           DeviceConfig.bluetoothName=deviceName
           binding.tvName.text = deviceName
       }
    }

    fun floatTest() {
        val str = "01020304"
        val strengthValue = intBitsToFloat(Integer.parseUnsignedInt(str, 16))
        val df: DecimalFormat = DecimalFormat("0.00")
        val result: String = df.format(strengthValue)
        Timber.d("转换后的值：${strengthValue}")

        // 1. 定义并初始化一个 float 变量
        val floatValue = 123.456f // 初始化 float 变量
        // 2. 使用 Float.floatToIntBits 方法获取 float 的位表示
        val bits = java.lang.Float.floatToIntBits(floatValue) // 将 float 转换为整数位表示
        // 3. 将位表示转换为 16 进制字符串
        val hexString = DataConversion.intToHex(bits) // 转换为 16 进制字符串
        // 4. 分离高位和低位并输出
        val highByte =
            if (hexString.length > 4) hexString.substring(0, hexString.length - 4) else "00" // 高位处理
        val lowByte =
            if (hexString.length > 4) hexString.substring(hexString.length - 4) else hexString // 低位处理
        Timber.d("HexString: $hexString") // 输出高位
        Timber.d("High Byte: $highByte") // 输出高位
        Timber.d("Low Byte: $lowByte") // 输出低位

        val hexString1 = "400921FB" // 16进制表示的浮点数
        val bytes = hexStringToByteArray(hexString)
        // 创建一个字节缓冲区，并设置为小端
        val buffer = ByteBuffer.wrap(bytes).order(ByteOrder.LITTLE_ENDIAN)
        val strengthValue1 = intBitsToFloat(Integer.parseUnsignedInt(hexString, 16))
        Timber.d("转换后的值：${strengthValue1}")
    }

}